package parser.symbol;

import utils.CompileError;

public class Symbol {
    // 认为表达式中单独的一个数字，比如2+3中的2是MyNumber const，value=2.i32，没有addr，没有name和id
    protected String type = "i32";    //i32  i1 默认i32
    protected boolean isConst = false; // 是否是常量 默认不是
    protected boolean isGlobal = false;
    protected String address;    //寄存器地址  带%或@
    protected String name;    // 变量名  比如 int a=1; 的a就是name，a的地址%v1
    protected int blockId; // 所在块编号，跟符号表中块编号对应

    private int initVal; //全局变量的初始值或者const变量的初始值


    public Symbol() {

    }

    public Symbol(String address) {
        this.address = address;
        this.blockId = Table.getInstance().getBlockId();
    }

    public boolean isI32() throws CompileError {
        if (type.equals("i32"))
            return true;
        else if (type.equals("i1"))
            return false;
        throw new CompileError("非i32和i1的未知类型");
    }

    public Symbol(String name, String address, String type) {
        this.name = name;
        this.address = address;
        this.type = type;
        this.blockId = Table.getInstance().getBlockId();
    }

    public Symbol(String name, boolean isConst, String type) {
        this.name = name;
        this.isConst = isConst;
        this.type = type;
        this.blockId = Table.getInstance().getBlockId();
    }


    public boolean isConst() {
        return isConst;
    }

    public boolean isGlobal() {
        return isGlobal;
    }

    public void setGlobal(boolean global) {
        isGlobal = global;
    }

    public void setAddress(String address) {
        this.address = address;
    }

    public void setBlockId(int blockId) {
        this.blockId = blockId;
    }

    public void setType(String type) {
        this.type = type;
    }

    public void setConst(boolean aConst) {
        isConst = aConst;
    }

    public String getType() {
        return type;
    }

    public String getAddress() {
        return address;
    }

    public String getPrintAddr() {
        if (this instanceof MyNumber) {
            return Integer.toString(((MyNumber) this).getValue());
        } else {
            return this.getAddress();
        }
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public int getInitVal() {
        return initVal;
    }

    public void setInitVal(int initVal) {
        this.initVal = initVal;
    }

    @Override
    public String toString() {
        if (this instanceof MyNumber)
            return "MyNumber{" +
                    "value=" + ((MyNumber) this).getValue() +
                    ", type='" + type + '\'' +
                    ", isConst=" + isConst +
                    ", isGlobal=" + isGlobal +
                    ", address='" + address + '\'' +
                    ", name='" + name + '\'' +
                    ", blockId=" + blockId +
                    "}\n";
        else if (this instanceof MyArray)
            return "MyArray{" +
                    "dim=" + ((MyArray) this).dim +
                    ", size=" + ((MyArray) this).size +
                    ", isConst=" + isConst +
                    ", isGlobal=" + isGlobal +
                    ", address='" + address + '\'' +
                    ", name='" + name + '\'' +
                    ", blockId=" + blockId +
                    "}\n";
        return "Symbol{" +
                "type='" + type + '\'' +
                ", isConst=" + isConst +
                ", address='" + address + '\'' +
                ", name='" + name + '\'' +
                ", blockId=" + blockId +
                "}\n";
    }
}
